package mysql

import (
	"data-transfer/domain"
	"sync/atomic"
)
import "context"

//GetNewsById 根据主键获取ANNOUNCEMENT
func (mdb *db) GetNewsById(ctx context.Context, id int64) (*domain.NEWS, error) {
	var results []*domain.NEWS
	err := mdb.db.NewSession().Where("ID=? ", id).Desc("ID").Find(&results)
	if err != nil {
		return nil, err
	}
	if len(results) > 0 {
		return results[0], nil
	}
	return nil, nil
}

//GetNews 获取所有资讯信息，用于插入infoService的Article表
func (mdb *db) GetNews(ctx context.Context) ([]*domain.NEWS, error) {
	var results []*domain.NEWS
	err := mdb.db.NewSession().Where("ID > 0 ").Desc("ID").Find(&results)
	return results, err
}

//InsertNews 插入快讯新闻基本信息
func (mdb *db) InsertNews(ctx context.Context, rows []*domain.NEWS) (int64, error) {
	var affected int64
	var err error
	execFun := func(index int) {
		r := rows[index]
		aff, e := mdb.db.NewSession().Insert(r)
		if e != nil {
			err = e
		}
		atomic.AddInt64(&affected, aff)
	}
	DoBatch(len(rows), 20, execFun)

	return affected, err
}

// InsertSkInfoChange 插入股票涨跌数据
func (mdb *db) InsertSkInfoChange(ctx context.Context, rows []*domain.SK_INFO_CHANGE) (int64, error) {
	checkSkInfoChangeDecimalNull(rows)
	var affected int64
	var err error
	execFun := func(index int) {
		r := rows[index]
		aff, e := mdb.db.NewSession().Insert(r)
		if e != nil {
			err = e
		}
		atomic.AddInt64(&affected, aff)
	}
	DoBatch(len(rows), 50, execFun)

	return affected, err
}

//InsertNewsSingle 插入快讯数据，用于goCanal监控
func (mdb *db) InsertNewsSingle(insertSql string, insertedMap map[string]interface{}) (int64, error) {
	var err error
	result, err := mdb.db.Exec(insertSql, insertedMap["ID"], insertedMap["NEWSTITLE_ME"], insertedMap["NEWSTEXT_ME"], insertedMap["NEWSSOURCE_ME"], insertedMap["PUBLISHTIME"], insertedMap["SYMBOL"], 0, 0, 0, 0, 0, 0, 0, insertedMap["EXCHANGE"], insertedMap["SORTTIME"], insertedMap["SOURCEKEY"])
	if err != nil {
		return 0, err
	}
	affected, err := result.RowsAffected()
	//affected, err := result.LastInsertId()
	return affected, err
}

//UpdateNews 更新快讯数据，用于goCanal监控
func (mdb *db) UpdateNews(updateSql string, updateMap map[string]interface{}) (int64, error) {
	var err error
	result, err := mdb.db.Exec(updateSql, updateMap["NEWSTITLE_ME"], updateMap["NEWSTEXT_ME"], updateMap["NEWSSOURCE_ME"], updateMap["PUBLISHTIME"], updateMap["SOURCEKEY"])
	if err != nil {
		return 0, err
	}
	affected, err := result.RowsAffected()
	return affected, err
}

//DeleteNews 删除快讯数据，用于goCanal监控
func (mdb *db) DeleteNews(deleteSql string, deleteMap map[string]interface{}) (int64, error) {
	var err error
	result, err := mdb.db.Exec(deleteSql, deleteMap["SOURCEKEY"])
	if err != nil {
		return 0, err
	}
	affected, err := result.RowsAffected()
	return affected, err
}

// InsertSkInfoChangeSingle 插入股票涨跌数据，用于goCanal监控
func (mdb *db) InsertSkInfoChangeSingle(insertSql string, insertedMap map[string]interface{}) (int64, error) {
	var err error
	result, err := mdb.db.Exec(insertSql, insertedMap["SYMBOL"], insertedMap["SENAME"], insertedMap["CHANGE"], insertedMap["PCHG"], insertedMap["EXCHANGE"])
	if err != nil {
		return 0, err
	}
	affected, err := result.RowsAffected()
	return affected, err

}

// UpdateSkInfoChange 更新股票涨跌数据，用于goCanal监控
func (mdb *db) UpdateSkInfoChange(updateSql string, updateMap map[string]interface{}) (int64, error) {
	var err error
	result, err := mdb.db.Exec(updateSql, updateMap["SENAME"], updateMap["CHANGE"], updateMap["PCHG"], updateMap["SYMBOL"])
	if err != nil {
		return 0, err
	}
	affected, err := result.RowsAffected()
	return affected, err
}

//DeleteSkInfoChange 删除股票涨跌数据，用于goCanal监控
func (mdb *db) DeleteSkInfoChange(deleteSql string, deleteMap map[string]interface{}) (int64, error) {
	var err error
	result, err := mdb.db.Exec(deleteSql, deleteMap["SYMBOL"])
	if err != nil {
		return 0, err
	}
	affected, err := result.RowsAffected()
	return affected, err
}

// HasNews 是否存在相应sourceKey的资讯新闻
func (mdb *db) HasNews(sourceKey string) (bool, error) {
	news := new(domain.NEWS)
	has, err := mdb.db.NewSession().Where("SOURCEKEY=? ", sourceKey).Get(news)
	return has, err
}

// checkSkInfoChangeDecimalNull 简单处理decimal 类型为空的情况
// TODO 后续更改为 https://github.com/shopspring/decimal
func checkSkInfoChangeDecimalNull(rows []*domain.SK_INFO_CHANGE) {
	defVal := "0.000000"
	for _, v := range rows {
		if v.Change == "" {
			v.Change = defVal
		}
		if v.Pchg == "" {
			v.Pchg = defVal
		}
	}
}
